package com.gitee.qdbp.general.trade.biz.personal.service;

import java.util.Arrays;
import java.util.List;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
import com.gitee.qdbp.able.exception.ServiceException;
import com.gitee.qdbp.able.jdbc.ordering.OrderPaging;
import com.gitee.qdbp.able.jdbc.paging.PageList;
import com.gitee.qdbp.able.result.ResultCode;
import com.gitee.qdbp.base.enums.Gender;
import com.gitee.qdbp.base.system.model.IAccount;
import com.gitee.qdbp.general.trade.api.personal.model.PersonalAddressBase;
import com.gitee.qdbp.general.trade.api.personal.model.PersonalAddressBean;
import com.gitee.qdbp.general.trade.api.personal.model.PersonalAddressUpdate;
import com.gitee.qdbp.general.trade.api.personal.model.PersonalAddressWhere;
import com.gitee.qdbp.general.trade.api.personal.service.IPersonalAddressExecutor;
import com.gitee.qdbp.general.trade.biz.personal.basic.PersonalAddressBasic;
import com.gitee.qdbp.tools.utils.VerifyTools;

/**
 * 用户地址业务处理类
 *
 * @author zhh
 * @version 180716
 */
@Service
@Transactional(propagation = Propagation.REQUIRED, rollbackFor = Throwable.class)
public class PersonalAddressExecutor implements IPersonalAddressExecutor {

    /** 日志对象 **/
    private static final Logger log = LoggerFactory.getLogger(PersonalAddressExecutor.class);

    @Autowired
    private PersonalAddressBasic personalAddressBasic;

    @Override
    public String create(PersonalAddressBase model, String userId, boolean isDefault, IAccount me)
            throws ServiceException {
        String msg = "Failed to create PersonalAddress. ";

        if (VerifyTools.isBlank(me)) {
            log.error(msg + "params is null: me");
            throw new ServiceException(ResultCode.PARAMETER_IS_REQUIRED);
        }
        if (VerifyTools.isBlank(model)) {
            log.error(msg + "params is null: model");
            throw new ServiceException(ResultCode.PARAMETER_IS_REQUIRED);
        }
        if (VerifyTools.isBlank(userId)) {
            log.error(msg + "params is null: userId");
            throw new ServiceException(ResultCode.PARAMETER_IS_REQUIRED);
        }

        if (model.getContactGender() == null) {
            model.setContactGender(Gender.UNKNOWN);
        }

        int total;
        { // 查询目前是否存在记录
            PageList<?> temp = personalAddressBasic.list(OrderPaging.COUNT);
            total = temp.getTotal();
        }

        int sortIndex = total == 0 || isDefault ? 0 : 1;
        { // 将现在的sortIndex向后移, 为新记录腾出空位
            PersonalAddressUpdate ud = new PersonalAddressUpdate();
            ud.setSortIndexAdd(1);
            PersonalAddressWhere w = ud.getWhere(true);
            w.setUserId(userId);
            w.setSortIndexMin(sortIndex);
            personalAddressBasic.update(ud, false);
        }

        PersonalAddressBean bean = model.to(PersonalAddressBean.class);
        // 业务逻辑
        bean.setId(null); // 主键由Basic生成, 不允许外部传入
        bean.setUserId(userId);
        bean.setSortIndex(sortIndex);

        // 向usr_personal_address表插入记录
        personalAddressBasic.create(bean);

        return bean.getId();
    }

    @Override
    public void update(String id, PersonalAddressBase model, IAccount me) throws ServiceException {
        String msg = "Failed to update PersonalAddress. ";

        if (VerifyTools.isBlank(me)) {
            log.error(msg + "params is null: me");
            throw new ServiceException(ResultCode.PARAMETER_IS_REQUIRED);
        }
        if (VerifyTools.isBlank(id)) {
            log.error(msg + "params is null: id");
            throw new ServiceException(ResultCode.PARAMETER_IS_REQUIRED);
        }
        if (VerifyTools.isBlank(model)) {
            log.error(msg + "params is null: model");
            throw new ServiceException(ResultCode.PARAMETER_IS_REQUIRED);
        }

        // 原始记录检查
        PersonalAddressBean older = personalAddressBasic.findById(id);
        if (older == null) {
            log.error(msg + "record is not found. id=" + id);
            throw new ServiceException(ResultCode.RECORD_NOT_EXIST);
        }

        PersonalAddressUpdate newer = createChangedModel(model, older);

        if (newer != null) {
            if (VerifyTools.isBlank(model.getTownship())) {
                newer.setTownshipToNull(true); // 如果新地址没有街道则修改为空
            }
            // 更新usr_personal_address表的记录
            personalAddressBasic.update(newer, false);
        }
    }

    /** 设置为默认地址 **/
    @Override
    public void setDefault(String id, IAccount me) throws ServiceException {
        String msg = "Failed to SetDefaultAddress. ";
        PersonalAddressBean older = personalAddressBasic.findById(id);
        if (older == null) {
            log.error(msg + "record is not found. id=" + id);
            throw new ServiceException(ResultCode.RECORD_NOT_EXIST);
        }
        if (older.getSortIndex() == 0) {
            return;
        }

        int sortIndex = older.getSortIndex();
        String userId = older.getUserId();
        { // 将当前记录之前的记录全部向后移动一格
            PersonalAddressUpdate ud = new PersonalAddressUpdate();
            ud.setSortIndexAdd(1);
            PersonalAddressWhere w = ud.getWhere(true);
            w.setUserId(userId);
            w.setSortIndexMax(sortIndex - 1);
            personalAddressBasic.update(ud, false);
        }
        { // 当前记录设置为0
            PersonalAddressUpdate ud = new PersonalAddressUpdate();
            ud.setSortIndex(0);
            PersonalAddressWhere w = ud.getWhere(true);
            w.setId(older.getId());
            personalAddressBasic.update(ud, true);
        }
    }

    @Override
    public void delete(String id, IAccount me) throws ServiceException {
        String msg = "Failed to delete PersonalAddress. ";

        if (VerifyTools.isBlank(me)) {
            log.error(msg + "params is null: me");
            throw new ServiceException(ResultCode.PARAMETER_IS_REQUIRED);
        }
        if (VerifyTools.isBlank(id)) {
            log.error(msg + "params is null: id");
            throw new ServiceException(ResultCode.PARAMETER_IS_REQUIRED);
        }

        // 从usr_personal_address表查询原记录
        PersonalAddressBean older = personalAddressBasic.findById(id);
        if (older == null) {
            log.error(msg + "record is not found.\n\tid is " + id);
            throw new ServiceException(ResultCode.RECORD_NOT_EXIST);
        }

        // 删除usr_personal_address表的记录
        personalAddressBasic.deleteByIds(Arrays.asList(id), false);
    }

    @Override
    public void delete(List<String> ids, IAccount me) throws ServiceException {
        String msg = "Failed to delete PersonalAddress. ";

        if (VerifyTools.isBlank(me)) {
            log.error(msg + "params is null: me");
            throw new ServiceException(ResultCode.PARAMETER_IS_REQUIRED);
        }
        if (VerifyTools.isBlank(ids)) {
            log.error(msg + "params is null: ids");
            throw new ServiceException(ResultCode.PARAMETER_IS_REQUIRED);
        }

        // 删除usr_personal_address表的记录
        personalAddressBasic.deleteByIds(ids, false);
    }

    /**
     * 创建一个新的对象, 只包含改动过的字段
     *
     * @author zhh
     * @param model 目标对象(一般是参数传入的)
     * @param older 源对象(一般是从数据库查询得到的)
     * @return 只包含有更新的字段对象
     */
    private PersonalAddressUpdate createChangedModel(PersonalAddressBase model, PersonalAddressBean older) {

        PersonalAddressUpdate newer = new PersonalAddressUpdate();
        boolean changed = false;
        newer.setId(older.getId()); // 主键

        if (VerifyTools.isChanged(model.getTagName(), older.getTagName())) {
            changed = true;
            newer.setTagName(model.getTagName()); // 标签: 如家,公司等
        }
        if (VerifyTools.isChanged(model.getContactName(), older.getContactName())) {
            changed = true;
            newer.setContactName(model.getContactName()); // 联系人姓名
        }
        if (VerifyTools.isChanged(model.getContactGender(), older.getContactGender())) {
            changed = true;
            newer.setContactGender(model.getContactGender()); // 性别(0.未知|1.男|2.女)
        }
        if (VerifyTools.isChanged(model.getContactPhone(), older.getContactPhone())) {
            changed = true;
            newer.setContactPhone(model.getContactPhone()); // 联系人电话
        }
        if (VerifyTools.isChanged(model.getAreaCode(), older.getAreaCode())) {
            changed = true;
            newer.setAreaCode(model.getAreaCode()); // 地区编号(关联行政区划表)
        }
        if (VerifyTools.isChanged(model.getAreaText(), older.getAreaText())) {
            changed = true;
            newer.setAreaText(model.getAreaText()); // 地区名称(由于地区编号经常会变, 需要保存地区名称)
        }
        if (VerifyTools.isChanged(model.getTownship(), older.getTownship())) {
            changed = true;
            newer.setTownship(model.getTownship()); // 乡镇或街道名称
        }
        if (VerifyTools.isChanged(model.getAddress(), older.getAddress())) {
            changed = true;
            newer.setAddress(model.getAddress()); // 详细地址
        }
        return changed ? newer : null;

    }

}
